use std::collections::HashSet;
use crate::db::dao::im_user_dao::{query_user_by_user_id, query_users_by_user_ids, user_inserts, user_total, user_updates};
use crate::db::db::Db;
use crate::db::db_transaction::transaction;
use crate::db::pojo::pojo::{ImUser};

pub struct ImUserService;

impl ImUserService {

    pub fn save_users(&self, users: &mut Vec<ImUser>) {
        let db = Db::open();
        transaction(db.clone(), move |db: Db| {
            self.save_users_business(db, users)
        });
    }
    
    pub fn total(&self)->usize {
        let db = Db::open();
        let total = transaction(db.clone(), move |db: Db| {
            user_total(db)
        });
        total
    }
    
    pub fn query_by_user_id(&self, user_id: &str) -> Option<ImUser> {
        let db = Db::open();
        query_user_by_user_id(db.clone(), user_id)
    }

    fn save_users_business(&self, db: Db, users: &mut Vec<ImUser>) {
        let user_ids = users.iter().map(|user| {user.user_id.clone()}).collect::<Vec<String>>();
        log::info!("db_users1: {:?}", &user_ids);
        let db_users = query_users_by_user_ids(db.clone(), user_ids);
        log::info!("db_users: {:?}", db_users);
        let db_ids = db_users.iter().map(|user| {&user.user_id}).collect::<HashSet<&String>>();
        let mut insert_users= Vec::new();
        let mut update_users = Vec::new();
        for user in users {
            let user_id = &user.user_id;
            if !db_ids.contains(user_id) {
                insert_users.push(user);
            } else {
                update_users.push(user);
            }
        }

        user_inserts(db.clone(), insert_users);
        user_updates(db.clone(), update_users);
    }
}
